﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace QuantitativeIndicator.FundStkRatio
{
    class FundStkRatioCaculator
    {
        public FundStkRatioDataModel FsrDB;
        public FundStkRatioCaculator()
        {
            this.FsrDB = new FundStkRatioDataModel();
        }
        //计算calDate的基金持有股票总市值变化率序列
        //需要考虑清楚的问题：
        //1. 
        public double[] caculatePortfolioRtn(string startDate, string endDate,string type, string isIndex, string fundInvestType)
        {
            string lastOneDate=FsrDB.getLastTradingDate(startDate);//startDate之前一交易日
            int dateNum = FsrDB.getTradedDatesNum(startDate, endDate);//得到计算收益的交易日个数
            double[] tmpValue=new double[dateNum+1];//计算dateNum个收益率需要dateNum+1个value数据
            double[] tmpRtn = new double[dateNum];

            List<string> tmpDateList =FsrDB.getTradingDateList(lastOneDate,endDate);//遍历从lastOneDate到endDate之间的所有交易日
            int i = 0;

            foreach (string tmpDate in tmpDateList)
            {
                string pfStartDate = FsrDB.getPortfolioStartDate(tmpDate);//组合成分股调整日,max(issueDate)
                Dictionary<string, double> tmpPF = FsrDB.getStartPortfolio(tmpDate, type, isIndex, fundInvestType);
                //特别注意组合成分调整日的收益率的处理
                string lastOneTmpDate = FsrDB.getLastTradingDate(tmpDate);//tmpDate之前一个交易日

                double startPrice = 0;
                double rtn = 0;
                double tmpLastValue = 0;

                if (pfStartDate == lastOneTmpDate)
                {
                    foreach (string tmpPortKey in tmpPF.Keys)
                    {
                        startPrice = FsrDB.getStockClosePrice(tmpPortKey, pfStartDate);
                        tmpLastValue = tmpLastValue + tmpPF[tmpPortKey] * startPrice;//对新生成组合往前推一个交易日
                        rtn = FsrDB.getStockIntervalIncrease(tmpPortKey, pfStartDate, tmpDate, "normal");
                        tmpValue[i] = tmpValue[i] + tmpPF[tmpPortKey] * startPrice * (1 + rtn);
                        // Console.WriteLine(tmpPortKey+","+tmpValue+","+startPrice+","+rtn);
                    }
                    if (i != 0)
                    {
                        tmpRtn[i - 1]= tmpValue[i] / tmpLastValue - 1;
                    }
                }
                else
                {
                    foreach (string tmpPortKey in tmpPF.Keys)
                    {
                        startPrice = FsrDB.getStockClosePrice(tmpPortKey, pfStartDate);
                        rtn = FsrDB.getStockIntervalIncrease(tmpPortKey, pfStartDate, tmpDate, "normal");
                        tmpValue[i] = tmpValue[i] + tmpPF[tmpPortKey] * startPrice * (1 + rtn);
                        // Console.WriteLine(tmpPortKey+","+tmpValue+","+startPrice+","+rtn);
                    }
                    if (i != 0)
                    {
                        tmpRtn[i-1] = tmpValue[i] / tmpValue[i - 1] - 1;
                    }
                }
                i++;
            }
            return tmpRtn;
        }
        //计算一天的指数收益率
        public double caculatePortfolioRtn(string calDate, string type, string isIndex, string fundInvestType)
        {
            string lastOneDate = FsrDB.getLastTradingDate(calDate);//startDate之前一交易日
            double[] tmpValue = new double[2];
            string[] dateList = new string[2];
            dateList[0] = lastOneDate;
            dateList[1] = calDate;
            double tmpRtn=0;

            for (int i = 0; i < 2; i++)
            {
                string tmpDate = dateList[i];
                string pfStartDate = FsrDB.getPortfolioStartDate(tmpDate);//组合成分股调整日,max(issueDate)
                Dictionary<string, double> tmpPF = FsrDB.getStartPortfolio(tmpDate, type, isIndex, fundInvestType);
                //特别注意组合成分调整日的收益率的处理
                string lastOneTmpDate = FsrDB.getLastTradingDate(tmpDate);//tmpDate之前一个交易日

                double startPrice = 0;
                double rtn = 0;
                double tmpLastValue = 0;

                if (pfStartDate == lastOneTmpDate)
                {
                    foreach (string tmpPortKey in tmpPF.Keys)
                    {
                        startPrice = FsrDB.getStockClosePrice(tmpPortKey, pfStartDate);
                        tmpLastValue = tmpLastValue + tmpPF[tmpPortKey] * startPrice;//对新生成组合往前推一个交易日
                        rtn = FsrDB.getStockIntervalIncrease(tmpPortKey, pfStartDate, tmpDate, "normal");
                        tmpValue[i] = tmpValue[i] + tmpPF[tmpPortKey] * startPrice * (1 + rtn);
                        // Console.WriteLine(tmpPortKey+","+tmpValue+","+startPrice+","+rtn);
                    }
                    if (i != 0)
                    {
                        tmpRtn = tmpValue[i] / tmpLastValue - 1;
                    }
                }
                else
                {
                    foreach (string tmpPortKey in tmpPF.Keys)
                    {
                        startPrice = FsrDB.getStockClosePrice(tmpPortKey, pfStartDate);
                        rtn = FsrDB.getStockIntervalIncrease(tmpPortKey, pfStartDate, tmpDate, "normal");
                        tmpValue[i] = tmpValue[i] + tmpPF[tmpPortKey] * startPrice * (1 + rtn);
                        // Console.WriteLine(tmpPortKey+","+tmpValue+","+startPrice+","+rtn);
                    }
                    if (i != 0)
                    {
                        tmpRtn = tmpValue[i] / tmpValue[i - 1] - 1;
                    }
                }
            }
            return tmpRtn;
        }
    }
}
